#include "ExecutiveFlybox.h"
#include "Executive.h"
#include "Data.h"
#include "Gfx.h"

#define FLYBOX_WAIT_IF_LESS_THAN_TIME 5
#define FLYBOX_WAIT_TIME 5

CExecutiveFlybox::CExecutiveFlybox(CData& rcData_, CGfx& rcGfx_)
    :
    CExecutive(rcData_, rcGfx_)
{
}

CExecutiveFlybox::~CExecutiveFlybox()
{
    CleanUp();
}


void CExecutiveFlybox::Init()
{
    // do bases's inits
    CExecutive::Init();

    // Check if Flybox opened, if not, open it
    if (!_cFly.InitFlybox())
        throw exception("Flybox cannot be started");

    _cFlyTimer.Reset();
}

bool CExecutiveFlybox::CheckForTrigger()
{
    bool bReturn = false;

    while (CheckForTriggerHelper()) // wait till trigger released
    {
        // we never go in here if trigger isn't pressed, but we'll only get out of it once trigger is released ;)
        bReturn = true;
    }

    return bReturn;
}

bool CExecutiveFlybox::CheckForTriggerHelper()
{
    if (_cFlyTimer.ElapsedTimeMilliSec()<FLYBOX_WAIT_IF_LESS_THAN_TIME) // make sure the next read doesn't occur too fast
        _cFlyTimer.WaitMilliSec(FLYBOX_WAIT_TIME);

    int nReturn = _cFly.IsTriggerDepressed();

    _cFlyTimer.Reset();                         // Flybox has just been read, reset timer

    if (nReturn==99)
        throw exception("CheckForTriggerHelper: Fatal Error: Flybox could not be read");
    else
        return nReturn==1;
}
void CExecutiveFlybox::UpdateDuringRun(const int& nCurrFrameIdx_)
{
    double dCurrControlState;

    // read current joystick position from Flybox and save it in data class
    dCurrControlState = _cFly.GetState()[0];
    if (dCurrControlState==99)
        throw exception("UpdateDuringRun: Fatal Error: Flybox could not be read");
    _cDist.SetControlValues()(nCurrFrameIdx_,0) = _rcData.ControlGain()[_tdCurrRun.ControlOrder()]*dCurrControlState;

    _cFlyTimer.Reset();                         // Flybox has just been read, reset timer

    // Call common method to finish Updating for this frame
    CExecutive::UpdateDuringRun(nCurrFrameIdx_);

    // sleep a bit if necessary, or we would be reading the flybox too fast - why the hell 11 is needed?
    // std::cout << _cFlyTimer.ElapsedTimeMilliSec() << std::endl;
    if (_cFlyTimer.ElapsedTimeMilliSec()<FLYBOX_WAIT_IF_LESS_THAN_TIME)
        _cFlyTimer.WaitMilliSec(FLYBOX_WAIT_TIME);
}

void CExecutiveFlybox::CleanUp()
{
    // Check if Flybox opened, if so, close it
    if (_cFly.IsFlyStarted())
        _cFly.rf_quit();
}